package com.googlecode.contests_repo.zip;

import java.io.File;
import java.io.IOException;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

import org.codehaus.jackson.JsonParseException;
import org.codehaus.jackson.map.JsonMappingException;
import org.codehaus.jackson.map.ObjectMapper;

import com.googlecode.contests_repo.anotation.ResourcePrivate;
import com.googlecode.contests_repo.core.model.Contest;
import com.googlecode.contests_repo.core.model.ReflectionUtils;
import com.googlecode.contests_repo.core.model.ResourcesUtils;
import com.googlecode.contests_repo.core.users.AccessRight;

/**
 * A {@link ResourceZiper} for {@link Contest}s. 
 * 
 * @author deni, boyan
 */
public class ContestZiper extends ResourceZiper {

	@Override
	public void processJsonFile(AccessRight right, String resourcePath,
			String zipPath, ZipOutputStream zip) throws JsonParseException, JsonMappingException, IOException {
		ObjectMapper mapper = new ObjectMapper();
		File contestJsonFile = new File(resourcePath, "contest.json");
		Contest contest = mapper.readValue(contestJsonFile, Contest.class);
		
		if (!right.includes(AccessRight.VIEW_FULL)) {
			ReflectionUtils.setAnnotatedFields(contest, ResourcePrivate.class, null);
		
			if (!ResourcesUtils.hasContestStarted(new File(resourcePath))) {
				contest.setProblemOrder(null);
				contest.setProblemScores(null);
			}
		}
		
		String path = getExtendedFilePath(zipPath, "contest.json");
		zip.putNextEntry(new ZipEntry(path));
		byte[] bytes = mapper.writeValueAsBytes(contest);
		zip.write(bytes);
	}

	@Override
	public ResourceZiper getChildZiper() {
		return new ProblemZiper();
	}
	
	protected boolean shouldIncludeChildResources(String resourcePath, AccessRight right) {
		if (!super.shouldIncludeChildResources(resourcePath, right)) {
			return false;
		}
		return right.includes(AccessRight.VIEW_FULL) ||
				ResourcesUtils.hasContestStarted(new File(resourcePath));
	}
	
	protected boolean shouldIncludePublicFiles(String resourcePath, AccessRight right) {
		if (!super.shouldIncludePublicFiles(resourcePath, right)) {
			return false;
		}
		return right.includes(AccessRight.VIEW_FULL) || 
			ResourcesUtils.hasContestStarted(new File(resourcePath));
	}
}
